﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Xml.Linq;

namespace TfsUtils
{
    public class XmlUtils
    {
        public String XmlDataFileDirectory { get; set; }

        public Boolean UpdateRequired { get; private set; }

        /// <summary>
        /// Initializes a new instance of the <see cref="XmlUtils"/> class, 
        /// witch stores data in the directory passed as arguments.
        /// </summary>
        /// <param name="xmlDataFileDirectory">The directory where the xml data file
        /// resides.</param>
        public XmlUtils(string xmlDataFileDirectory)
        {
            XmlDataFileDirectory = xmlDataFileDirectory;
        }


        private Dictionary<String, XDocument> _docs = new Dictionary<string, XDocument>();
        private string _fileName;

        public Int32 GetIdForValue(string stringValue, String categoryName)
        {
            XDocument doc = null;
            if (_docs.ContainsKey(categoryName))
            {
                doc = _docs[categoryName];
            }
            else
            {
                //load from disk if exists or create a new one.
                string savedFile = Path.Combine(XmlDataFileDirectory, categoryName + ".xml");
                if (!File.Exists(savedFile))
                {
                    //file does not exists.
                    doc = new XDocument();
                    doc.Add(new XElement(categoryName,
                        new XElement("element",
                            new XAttribute("value", stringValue),
                            new XAttribute("id", 1))));
                    UpdateRequired = true;
                }
                else
                {
                    doc = XDocument.Load(new StringReader(File.ReadAllText(savedFile)));
                }
                _docs.Add(categoryName, doc);
            }

            var element = doc.Descendants("element")
                .Where(e => e.Attribute("value").Value == stringValue);
            if (element.Count() == 0)
            {
                //we does not have element, should take the maximum one and then add 
                //one.
                var newValue = doc.Descendants("element")
                                   .Select(e => Int32.Parse(e.Attribute("id").Value))
                                   .Max() + 1;
                doc.Root.Add(new XElement("element",
                            new XAttribute("value", stringValue),
                            new XAttribute("id", newValue)));
                UpdateRequired = true;
                return newValue;
            }

            return Int32.Parse(element.Single().Attribute("id").Value);
        }

        public void Save()
        {
            foreach (var xDocument in _docs)
            {
                _fileName = GetFileNameForCategory(xDocument.Key);
                File.WriteAllText(_fileName, xDocument.Value.ToString());
            }
        }

        public string GetFileNameForCategory(string categoryName)
        {
            return Path.Combine(XmlDataFileDirectory, categoryName + ".xml");
        }
    }
}
